using System;
using System.Collections.Generic;
using System.Linq;
using System.ServiceModel;
using System.Web.Caching;
using AutoMapper;
using Core;
using IglooCoder.Commons.WcfNhibernate;
using Infrastucture;
using WcfService1.DTO;
using Omu.ValueInjecter;

namespace WcfService1
{
    // NOTE: You can use the "Rename" command on the "Refactor" Customer to change the class name "CustomerServices" in code, svc and config file together.
    [ServiceBehavior(InstanceContextMode = InstanceContextMode.PerCall)]
    [NHibernateContext]
    public class CustomerServices : ICustomerServices
    {
        private readonly CustomerRepository CustomerRepository;
        private Cache cache;
        private WcfSessionStorage _session;
        public CustomerServices()
        {
            _session = new WcfSessionStorage();
            CustomerRepository = new CustomerRepository(_session);
            cache = new Cache();
        }

        #region ICustomerServices Members

        public List<CustomerDTO> GetList(int page, out long recordCount, string sortProperty = null,
                                         string sortType = "ASC")
        {
            var Customers = new List<Customer>();
            var Results = new List<CustomerDTO>();

            if (string.IsNullOrEmpty(sortProperty))
            {
                Customers = CustomerRepository.GetDataPaged(page, 30).ToList();
            }
            else
            {
                Customers = CustomerRepository.GetDataPaged(page, 30, sortProperty, sortType).ToList();
            }

            recordCount = CustomerRepository.RecordCount;

            Customers.ForEach(x =>
                                  {
                                      var customerDto = new CustomerDTO();
                                      customerDto.InjectFrom(x);
                                      customerDto.Coa = new CoaDTO();
                                      if (x.Coa != null) customerDto.Coa.InjectFrom(x.Coa);
                                      Results.Add(customerDto);
                                  }
                );

            return Results;
        }

        public bool Save(CustomerDTO CustomerDTO,String mode)
        {
            bool res;
            try
            {
                Customer Customer = CustomerRepository.GetDataOne(x => x.CustomerId == CustomerDTO.CustomerId);
                if (mode == "Add")
                    if (Customer != null) throw new Exception("Customer Sudah Ada!");
                if (Customer == null)
                {
                    Customer = new Customer();
                }
                Mapper.Map(CustomerDTO, Customer);
                CustomerRepository.SaveOrUpdate(Customer);
                res = true;
            }
            catch (Exception ex)
            {
                throw ex;
            }

            return res;
        }


        public bool Delete(CustomerDTO CustomerDto)
        {
            bool res=false;
            try
            {
                var customer = CustomerRepository.GetDataOne(x => x.CustomerId == CustomerDto.CustomerId);
                var salesInvoiceRepository = new SalesInvoiceRepository(_session);
                var si = salesInvoiceRepository.GetDataOne(x => x.Customer.CustomerId == CustomerDto.CustomerId);
                if (si != null) return res;
                CustomerRepository.Delete(customer);
                res = true;
            }
            catch (Exception)
            {
                res = false;
            }

            return res;
        }


        public List<CustomerDTO> GetListByCriteria(Dictionary<String, Object> criteria, string expression, int page,
                                                   out long recordCount)
        {
            var Customers = new List<Customer>();
            var Results = new List<CustomerDTO>();
            Customers = CustomerRepository.GetDataPaged(criteria, expression, page, 30).ToList();
            recordCount = CustomerRepository.RecordCount;
            Customers.ForEach(x =>
                                  {
                                      var customerDto = new CustomerDTO();
                                      customerDto.InjectFrom(x);
                                      customerDto.Coa = new CoaDTO();
                                      if (x.Coa != null) customerDto.Coa.InjectFrom(x.Coa);
                                      Results.Add(customerDto);
                                  }
                );

            return Results;
        }


        public List<CustomerDTO> GetAllCustomer()
        {
            //if (cache["Customers"] != null)
            //    return cache["Customers"] as List<CustomerDTO>;

            List<Customer> Customers = CustomerRepository.FetchAll().ToList();
            var Results = new List<CustomerDTO>();
            Customers.ForEach(x =>
                                  {
                                      var customerDto = new CustomerDTO();
                                      customerDto.InjectFrom(x);
                                      customerDto.Coa = new CoaDTO();
                                      if (x.Coa != null) customerDto.Coa.InjectFrom(x.Coa);
                                      Results.Add(customerDto);
                                  }
                );

            return Results;
        }


        public CustomerDTO GetCustomer(String kodeCustomer)
        {
            Customer Customer = CustomerRepository.GetDataOne(x => x.CustomerId == kodeCustomer);
            var customerDto = new CustomerDTO();
            customerDto.InjectFrom(Customer);
            customerDto.Coa = new CoaDTO();
            if (Customer.Coa != null) customerDto.Coa.InjectFrom(Customer.Coa);
            return customerDto;
        }

        public List<CustomerDTO> GetCustomerList(string NamaCustomer)
        {
            if (string.IsNullOrEmpty(NamaCustomer)) return new List<CustomerDTO>();
            List<Customer> Customers =
                CustomerRepository.GetDataList(x => x.CustomerName.Contains(NamaCustomer)).ToList();
            List<CustomerDTO> Results = (from c in Customers
                                         orderby c.CustomerName
                                         select
                                             new CustomerDTO
                                                 {
                                                     CustomerId = c.CustomerId,
                                                     CustomerName = c.CustomerName,
                                                     Address = c.Address
                                                 })
                .ToList();


            return Results;
        }

       public void ImporCustomer(List<CustomerDTO> customers)
       {
           List<Customer> Customers = (from c in customers
                                       select new Customer()
                                                  {
                                                      CustomerId = c.CustomerId,
                                                      CustomerName = c.CustomerName,
                                                      Address = c.Address,
                                                      City = c.City,
                                                      PostalCode = c.PostalCode,
                                                      Country = c.Country,
                                                      Telp = c.Telp,
                                                      Fax = c.Fax,
                                                      Email = c.Email,
                                                      ContactPerson = c.ContactPerson
                                                  }).ToList();
           CustomerRepository.InsertRange(Customers);
       }

        #endregion
    }
}